<template>
  <div class="app">
    <div class="app-header">
      <NavMenu />
    </div>
    <router-view/>
    <div class="app-wrapper">
      <LoginItem />
      <MyProfileItem />
    </div>
  </div>
</template>

<script>
  import { mapState } from 'vuex';
  import NavMenu from './components/utils/NavMenu.vue';
  import LoginItem from './components/user/LoginItem.vue';
  import MyProfileItem from './components/user/MyProfileItem.vue';
  import { STATUS,ACTION,VERSION } from './utils/trtcCustomMessageMap';

  export default {
    name: 'App',
    data () {
      return {
        msg: 'Hello World'
      }
    },
    components:{
      NavMenu,
      LoginItem,
      MyProfileItem
    },
    computed: {
      ...mapState({
        isSDKReady: state => state.user.isIMSDKReady,
        videoCallStatus: state => state.videocall.videoCallStatus
      })
    },
    mounted() {
      // 初始化监听器
      this.initListener();
    },
    methods: {
      initListener(){
        this.tim.on(this.TIM.EVENT.SDK_READY, this.onReadyStateUpdate, this);
        this.tim.on(this.TIM.EVENT.SDK_NOT_READY, this.onReadyStateUpdate, this);
        this.tim.on(this.TIM.EVENT.KICKED_OUT, this.onKickedOut);
        this.tim.on(this.TIM.EVENT.ERROR, this.onError);
        this.tim.on(this.TIM.EVENT.MESSAGE_RECEIVED, this.onReceiveMessage);
        this.tim.on(this.TIM.EVENT.CONVERSATION_LIST_UPDATED, this.onConversationListUpdated);
        this.tim.on(this.TIM.EVENT.GROUP_LIST_UPDATED,this.onGroupListUpdate);
      },
      onReadyStateUpdate(event) {
        const isSDKReady = event.name === this.TIM.EVENT.SDK_READY ? true : false;
        this.$store.commit('toggleIsSDKReady', isSDKReady);

        if (isSDKReady) {
          this.$store.dispatch('getMyProfile');
        } else {
          this.$store.commit('showMessage', { message: 'SDK_NOT_READY', type: 'error' });
        }
      },
      onKickedOut() {
        this.$store.commit('showMessage', { message: '被踢出，请重新登录。', type: 'error' });
        this.$store.commit('toggleIsLogin', false);
        this.$store.commit('reset');
      },
      onError(event) {
        if (event.data.message !== 'Network Error') {
          this.$store.commit('showMessage', { message: event.data.message, type: 'error' });
        }
      },
      onReceiveMessage(event) {
        this.handleVideoMessage(event.data);
        this.$store.commit('pushCurrentMessageList', event.data);
      },
      onConversationListUpdated(event) {
        this.$store.commit('updateConversationList', event.data);
      },
      onGroupListUpdate(event) {
        this.$store.commit('updateGroupList', event.data);
      },
      handleVideoMessage(messageList){
        // 筛选出自定义消息，并且data === 'video_call'
        const videoMessageList = messageList.filter(
          message => message.type === this.TIM.TYPES.MSG_CUSTOM && message.payload.data === 'video_call'
        );
        // 若没有video_call的消息，return
        if (videoMessageList.length === 0) return;
        let videoPayload = {};
        try{
          videoPayload = JSON.parse(videoMessageList[0].payload.extension);
        } catch(e) {
          videoPayload = {};
        }
        switch (videoPayload.action) {
          case ACTION.VIDEO_CALL_ACTION_DIALING: 
            // 收到通话请求时，判断当前是否空闲状态
            // 空闲状态，进入被呼叫状态
            // 非空闲状态，发送消息，告知对方忙线中
            if(this.videoCallStatus === STATUS.VIDEO_CALL_STATUS_FREE){
              this.$store.dispatch('checkoutConversation',videoMessageList[0].conversationID);// 切换当前会话页
              this.$store.commit('toggleVideoCallStatus', STATUS.VIDEO_CALL_STATUS_CALLED);
            } else {
              const options = {
                room_id: videoPayload.room_id,
                action: ACTION.VIDEO_CALL_ACTION_LINE_BUSY,
                type: videoMessageList[0].conversationType,
                duration: 0,
                version: VERSION
              }
              const message = this.tim.createCustomMessage({
                to: videoMessageList[0].from,
                conversationType: videoMessageList[0].conversationType,
                payload: {
                  data: 'video_call',
                  description: '',
                  extension: JSON.stringify(options)
                }
              });
              this.$store.dispatch('sendMessage', message);
            }
            break;
          case ACTION.VIDEO_CALL_ACTION_ACCEPTED: // 对方接受通话，进入通话页面
            this.$store.commit('toggleVideoCallStatus', STATUS.VIDEO_CALL_STATUS_CALLING);
            break;
          case ACTION.VIDEO_CALL_ACTION_SPONSOR_CANCEL:
          case ACTION.VIDEO_CALL_ACTION_REJECT:
          case ACTION.VIDEO_CALL_ACTION_SPONSOR_TIMEOUT:
          case ACTION.VIDEO_CALL_ACTION_HANGUP: 
          case ACTION.VIDEO_CALL_ACTION_LINE_BUSY:
          case ACTION.VIDEO_CALL_ACTION_ERROR:
            // 结束通话
            this.$store.commit('toggleVideoCallStatus', STATUS.VIDEO_CALL_STATUS_FREE);
            break;
          default: // 未知
            this.$store.commit('toggleVideoCallStatus', STATUS.VIDEO_CALL_STATUS_FREE);
            break;
        }
      }
    }
  }
</script>

<style>
html,body,.app{
  height: 100%;
}
body, h1, h2, h3, h4, h5, h6, hr, p, blockquote, dl, dt, dd, ul, ol, li, pre, form, fieldset, legend, button, input, textarea, th, td { margin:0; padding:0; }
ul, ol { 
  list-style: none; 
}
a { 
  text-decoration: none; 
}
a:hover { 
  text-decoration: underline; 
}
.router-link-active {
  text-decoration: none;
}
.app-header {
  position: relative;
  width: 100%;
  z-index: 9999;
}
body{
  /* 加载背景图 */
  background-image: url("./assets/image/backgroup.jpg");
  /* 背景图垂直、水平均居中 */
  background-position: center center;
  /* 背景图不平铺 */
  background-repeat: no-repeat;
  /* 当内容高度大于图片高度时，背景图像的位置相对于viewport固定 */
  background-attachment: fixed;
  /* 让背景图基于容器大小伸缩 */
  background-size: cover;
  /* 设置背景颜色，背景图加载过程中会显示背景色 */
  background-color: #eee;
}
/* 设置滚动条的样式 */
::-webkit-scrollbar {
  width: 3px;
  height: 3px;
}
/* 滚动槽 */
::-webkit-scrollbar-track {
  border-radius: 10px;
}
/* 滚动条滑块 */
::-webkit-scrollbar-thumb {
  border-radius: 10px;
  background: rgba(0, 0, 0, 0.1);
}
</style>
